#ifndef VSSERVER_H
#define VSSERVER_H

#include "vsGlobal.h"
#include <QTcpServer>
#include <QImage>

class vsFileServeTask;
class vsSocketWrapper;
class vsNetHeader;


const qint64 c_clear_byterate_stats = -666;


struct vsNetworkMediaInfo
{
    QString id;
    QString key;
    QString path;
    QString mime;

    QStringMap   tags;
    QHostAddress host;

    QByteArray poster;     // pic binary
    QSize      posterSize; // pic width & height
    QString    posterMime;

    qint64 size;
    qint64 duration;
};

class vsInfoController
{
public:
    explicit vsInfoController() {}
    virtual ~vsInfoController() {}

    virtual bool canServeID(QString id) = 0;
    virtual bool getMediaInfo(vsNetworkMediaInfo &i) = 0;
};


//-------------------------------------------------------------------
class vsServer : public QTcpServer
{
    Q_OBJECT

public:
    explicit vsServer(vsInfoController *infc, QObject *parent = 0);
    ~vsServer();

    void setMaxUploadRate  (int bytes_per_second);  /// zero or less for unlimited
    void setMaxDownloadRate(int bytes_per_second);

    inline int maxUploadRate()   { return upLimit; }
    inline int maxDownloadRate() { return dlLimit; }

    void stop();
    bool startAtPort(int port);

    inline int port() { return localPort; }

public slots:
    void onNewConnection(); /// knock-knock Neo
    void onSocketReady();
    void onSocketBytesSent(qint64 count);

    void transfer();
    void cheduleTransfer();

    void onSocketError();
    void onFileServeTaskError();
    void onTransferComplete();

    void onURLChanged(QString new_url);

signals:
    void transmitted(QString path, qint64 bytesSent);

protected:
    QString server_url;

    int upLimit;
    int dlLimit;

    int localPort;
    bool listening;

    bool cheduledTransfer;

    vsInfoController *ic;

    QLinkedList<vsFileServeTask*> fileServeTasks;

    QStringMap mimes;

    bool serveMedia (vsNetHeader *h, QTcpSocket *s, QString id);
    bool serveJSON  (vsNetHeader *h, QTcpSocket *s, QString id);
    bool serveHTML  (vsNetHeader *h, QTcpSocket *s, QString id);
    bool serveStatic(vsNetHeader *h, QTcpSocket *s, QString name);
    bool servePoster(vsNetHeader *h, QTcpSocket *s, QString /*id*/);
    bool serveRobots(vsNetHeader *h, QTcpSocket *s);
};

#endif // VSSERVER_H
